package com.refresh;

import android.content.Context;
import android.util.AttributeSet;
import android.util.Log;
import android.view.MotionEvent;
import android.view.View;
import android.view.animation.Animation;
import android.view.animation.RotateAnimation;
import android.widget.AbsListView;
import android.widget.ListView;
import android.widget.ProgressBar;
import android.widget.TextView;

import java.text.SimpleDateFormat;

/**
 * Created by Administrator on 2017/12/18.
 */

public class RefreshListView extends ListView implements AbsListView.OnScrollListener {
    View mHeaderVIew;
    View mHeaderArrow;
    TextView mTitleText;
    TextView mStateDesc;
    ProgressBar pb;
    // paddingtop + moveDown
    int paddingTop;
    int headerViewHeight;

    RotateAnimation rotateUpAnimation;
    RotateAnimation rotateDownAnimation;

    float downY, moveY;
    public static final int PULL_TO_REFRESH = 0; //下拉刷新
    public static final int RELEASE_REFRESH = 1;// 释放刷新
    public static final int REFRESHING = 2; //刷新中
    int currentState = PULL_TO_REFRESH;
    private OnRefreshListener listener;
    private View mFooterVIew;
    private int footerViewHeight;
    private boolean isLoadMore;

    public RefreshListView(Context context) {
        super(context);
        init();
    }

    public RefreshListView(Context context, AttributeSet attrs) {
        super(context, attrs);
        init();

    }

    public RefreshListView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        init();
    }

    /**
     * 初始化头布局,脚布局
     * 滚动监听
     */
    private void init() {
        initHeaderView();
        initAnimation();
        initFooterView();
        setOnScrollListener(this);
    }


    /**
     * 初始化头布局动画
     */
    private void initAnimation() {
        //向上转,逆时针旋转0 ->  -180

        rotateUpAnimation = new RotateAnimation(0f, -180f,
                Animation.RELATIVE_TO_SELF, 0.5f,
                Animation.RELATIVE_TO_SELF, 0.5f);
        rotateUpAnimation.setDuration(300);
        rotateUpAnimation.setFillAfter(true); //动画停留在结束位置

        //向上转,逆时针旋转-180 ->  -360

        rotateDownAnimation = new RotateAnimation(-180f, -360f,
                Animation.RELATIVE_TO_SELF, 0.5f,
                Animation.RELATIVE_TO_SELF, 0.5f);
        rotateDownAnimation.setDuration(300);
        rotateDownAnimation.setFillAfter(true); //动画停留在结束位置
    }


    /**
     * 初始化头布局
     */
    private void initHeaderView() {
        //

        mHeaderVIew = View.inflate(getContext(), com.refresh.R.layout.layout_header_list, null);
        mHeaderArrow = mHeaderVIew.findViewById(R.id.iv_arrow);
        mTitleText = mHeaderVIew.findViewById(R.id.title);
        mStateDesc = mHeaderVIew.findViewById(R.id.tv_desc_last_refresh);
        pb = mHeaderVIew.findViewById(R.id.pb);
        //提前手动测量高度
        mHeaderVIew.measure(0, 0);//按照设置的规则测量

        //设置内边距 ,可以隐藏当前控件  -自身高度

        headerViewHeight = mHeaderVIew.getMeasuredHeight();
        //    Log.e("执行", "initHeaderView: height: " + height + "---headerViewHeight: " + headerViewHeight);
        // TODO: 2017/12/18 结果两个值都是0,因为是在构造方法中执行的,需要先调用onMeasure方法

        //修改paddingTop的高度来实现
        mHeaderVIew.setPadding(0, -headerViewHeight, 0, 0);
        addHeaderView(mHeaderVIew);
    }

    private void initFooterView() {
        mFooterVIew = View.inflate(getContext(), com.refresh.R.layout.layout_footer_list, null);
        mFooterVIew.measure(0, 0);
        footerViewHeight = mFooterVIew.getMeasuredHeight();
        mFooterVIew.setPadding(0, -footerViewHeight, 0, 0);

        addFooterView(mFooterVIew);
    }

    @Override
    public boolean onTouchEvent(MotionEvent ev) {
        //判断滑动距离,给header设置paddingTop
        switch (ev.getAction()) {
            case MotionEvent.ACTION_DOWN:

                downY = ev.getY();
                break;
            case MotionEvent.ACTION_MOVE:
                moveY = ev.getY();

                //如果是正在刷新中,就执行父类的处理
                if (currentState == REFRESHING) {
                    return super.onTouchEvent(ev);
                }


                float offset = moveY - downY;
                //  int paddingTop = -自身高度 + 偏移量
                //只有偏移量>0,并且当前第一个可见条目索引是0,才放大头部
                if (offset > 0 && getFirstVisiblePosition() == 0) {
                    int paddingTop = (int) (-headerViewHeight + offset);
                    mHeaderVIew.setPadding(0, paddingTop, 0, 0);
                    if (paddingTop >= 0 && currentState != RELEASE_REFRESH) {//防止频繁调用刷新状态,要做动画
                        //变成释放刷新状态
                        currentState = RELEASE_REFRESH;
                        Log.e("执行", "释放刷新: " + currentState);

                        updateHeader();//根据最新的状态值更新头布局内容

                    } else if (paddingTop < 0 && currentState != PULL_TO_REFRESH) {
                        //切换成下拉刷新状态
                        currentState = PULL_TO_REFRESH;
                        Log.e("执行", "刷新状态: " + currentState);
                    }
                    return true; //当前事件被我们处理并消费
                }

                break;
            case MotionEvent.ACTION_UP:
                if (currentState == PULL_TO_REFRESH) {
                    mHeaderVIew.setPadding(0, -headerViewHeight, 0, 0);
                    ;
                } else if (currentState == RELEASE_REFRESH) {
                    mHeaderVIew.setPadding(0, 0, 0, 0);
                    currentState = REFRESHING;
                    updateHeader();
                }

                break;
        }
        return super.onTouchEvent(ev);

    }

    private void updateHeader() {
        switch (currentState) {
            case PULL_TO_REFRESH: //切换回下拉刷新
                mHeaderArrow.startAnimation(rotateDownAnimation);
                mTitleText.setText("下拉刷新");
                break;
            case RELEASE_REFRESH: //切换成释放刷新
                //做动画,改标题
                mHeaderArrow.startAnimation(rotateUpAnimation);
                mTitleText.setText("释放刷新");

                break;
            case REFRESHING: // 刷新中...
                mHeaderArrow.clearAnimation();
                mHeaderArrow.setVisibility(INVISIBLE);
                pb.setVisibility(VISIBLE);
                mTitleText.setText("正在刷新中...");

                if (listener != null) {
                    listener.onRefresh(); //通知调用者,让其到网络加载数据
                }

                break;

        }
    }

    public void onRefreshComplete() {
        if (isLoadMore) {
            mFooterVIew.setPadding(0, -footerViewHeight, 0, 0);
            isLoadMore = false;
        } else {
            currentState = PULL_TO_REFRESH;
            mTitleText.setText("下拉刷新");
            mHeaderVIew.setPadding(0, -headerViewHeight, 0, 0);
            pb.setVisibility(INVISIBLE);
            mHeaderArrow.setVisibility(VISIBLE);
            String time = getTime();
            mStateDesc.setText("最后刷新时间:" + time);
        }


    }

    public String getTime() {
        long currentTime = System.currentTimeMillis();

        SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");

        return simpleDateFormat.format(currentTime);
    }

    /*  public static int SCROLL_STATE_IDLE = 0;  空闲

    public static int SCROLL_STATE_TOUCH_SCROLL = 1;  //触摸滑动

    public static int SCROLL_STATE_FLING = 2; //滑翔
    */

    @Override
    public void onScrollStateChanged(AbsListView view, int scrollState) {
        //状态更新的时候
        Log.e("执行", "onScrollStateChanged: scrollState" + scrollState);
        if (isLoadMore) {
            return; //已经在加载更多,返回
        }

        //最新状态是空闲状态,并且当前界面显示了所有数据的最后一条,加载更多
        if (scrollState == SCROLL_STATE_IDLE && getLastVisiblePosition() >= (getCount() - 1)) {
            isLoadMore = true;
            Log.e("执行", "onScrollStateChanged: 开始加载更多");
            mFooterVIew.setPadding(0, 0, 0, 0);
            setSelection(getCount()); //自动显示加载更多

            if (listener != null) {
                listener.onLoadMore();
            }
        }
    }

    @Override
    public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount, int totalItemCount) {
        //滑动过程
    }

    public interface OnRefreshListener {
        void onRefresh();

        void onLoadMore();
    }

    public void setRefreshListener(OnRefreshListener listener) {
        this.listener = listener;
    }
}